home *** CD-ROM | disk | FTP | other *** search
/ Linux Cubed Series 8: LINUX Games / Linux Cubed Series 8 - LINUX Games.iso / games / x11 / video / xevil-1.000 / xevil-1 / test.h < prev    next >
C/C++ Source or Header  |  1995-02-08  |  20KB  |  804 lines

  1. /*    Copyright (C) 1994  Steve Hardt
  2.  
  3.       This program is free software; you can redistribute it and/or modify
  4.       it under the terms of the GNU General Public License as published by
  5.       the Free Software Foundation; either version 1, or (at your option)
  6.       any later version.
  7.  
  8.       This program is distributed in the hope that it will be useful,
  9.       but WITHOUT ANY WARRANTY; without even the implied warranty of
  10.       MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  11.       GNU General Public License for more details.
  12.  
  13.       You should have received a copy of the GNU General Public License
  14.       along with this program; if not, write to the Free Software
  15.       Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  16.  
  17.       Steve Hardt 
  18.       hardts@athena.mit.edu (or hardts@r4002.3dem.bioch.bcm.tmc.edu)
  19.       2043 McClendon
  20.       Houston, TX 77030
  21.       */
  22.  
  23. #ifndef PHYSICAL_HH
  24. #define PHYSICAL_HH
  25.  
  26. #pragma interface
  27.  
  28.  
  29. // Include Files
  30. #include "utils.h"
  31. #include "coord.h"
  32. #include "area.h"
  33. #include "world.h"
  34. #include "id.h"
  35. #include "intel.h"
  36. #include "locator.h"
  37.  
  38.  
  39. // Defines
  40. #define PH_ANIM_MAX 4
  41. #define PH_FRAME_MAX 7
  42. #define PH_WEAPONS_MAX 10
  43. #define PH_ITEMS_MAX 20
  44. #define PH_AMMO_UNLIMITED -1
  45. #define PH_CORPSE_TIME 400
  46.  
  47.  
  48.  
  49. // Other declarations
  50. enum PHsig {PH_NO_SIG, PH_NOT_SET, PH_ID_CHANGED};
  51.  
  52.  
  53.  
  54. // Class declarations
  55.  
  56. ////////// Physical
  57. /* The parent class of all physical objects. */
  58.  
  59. struct PhysicalContext {
  60.   Health health;
  61.   Mass mass;
  62.   ClassId classId;
  63.   const char *clas;
  64. };
  65.  
  66.  
  67. class Physical {
  68. public:
  69.   Physical(const PhysicalContext &,WorldP,LocatorP);
  70.   /* EFFECTS: Create a new, mapped physical with no Id with undefined area. */
  71.  
  72.   Physical();
  73.   /* NOTE: Should never be called. */
  74.  
  75.   virtual ~Physical();
  76.  
  77.   virtual const Area &get_area() = 0;
  78.   Health get_health() {return health;}
  79.   Health get_health_max() {return pc->health;}
  80.   Mass get_mass() {return mass;}
  81.   virtual Vel get_vel();
  82.   virtual Dir get_dir();
  83.  
  84.   ClassId get_class_id() {return pc->classId;}
  85.   const char *identify() {return pc->clas;}
  86.  
  87.   virtual int get_drawing_level();
  88.  
  89.   Boolean delete_me() {return deleteMe;}
  90.  
  91.   Boolean alive() {return health >= 0;}
  92.   /* NOTE: Is publicly known that (health >= 0) <=> alive.  So this function is
  93.    just for convenience. */
  94.  
  95.   /* Should only be used for abstract classes.  Actual classes can be tested
  96.      for with get_class_id(). */
  97.   virtual Boolean is_moving();
  98.   virtual Boolean is_shot();
  99.   virtual Boolean is_item(); 
  100.   virtual Boolean is_bomb();
  101.   virtual Boolean is_weapon();
  102.   virtual Boolean is_cutter();
  103.   virtual Boolean is_gun();
  104.   virtual Boolean is_creature(); 
  105.   virtual Boolean is_user();
  106.   virtual Boolean is_fighter();
  107.   virtual Boolean is_walking(); 
  108.   virtual Boolean is_sticky(); 
  109.   virtual Boolean is_flying();
  110.  
  111.   Boolean get_mapped() {return mapped;}
  112.  
  113.   virtual Boolean collidable();
  114.   /* NOTE: This value never changes for an object. */
  115.  
  116.   const Acc *get_unit_accs() {return unitAccs;}
  117.   const Vel *get_unit_vels() {return unitVels;}
  118.  
  119.   Id get_id() {assert(idValid); return id;}
  120.  
  121.   PHsig get_id(Id &id);
  122.   /* MODIFIES: id */
  123.   /* EFFECTS: Set id to be the Id and return PH_NO_SIG if set.  Otherwise, 
  124.      return PH_NOT_SET. */
  125.  
  126.   PhysicalP get_dont_collide() {return dontCollide;}
  127.   /* EFFECTS: If there is another object that *this is not allowed to collide
  128.      with, return it.  Otherwise return NULL; */
  129.  
  130.   IntelP get_intel() {return intel;}
  131.   /* NOTE: Can be NULL. */
  132.  
  133.   void set_command(ITcommand c) {command = c;}
  134.   /* EFFECTS: Sets the command to be c, overrides any previous command 
  135.      setting. */
  136.   /* NOTE: command is not clocked. */
  137.  
  138.   PHsig set_id(const Id &id);
  139.   /* EFFECTS: Set the Id to be id.  Return PH_NO_SIG if there was no previous
  140.      id.  Return PH_ID_CHANGED if there was a previous id.  The id is set in 
  141.      either case. */
  142.  
  143.   void set_dont_collide(PhysicalP other) {dontCollide = other;}
  144.   /* EFFECTS: *this will not be allowed to collide with other.  Any previous 
  145.      value will be overridden.  A setting of NULL disables this feature. */
  146.  
  147.   void set_intel(IntelP i) {intel = i;  if (i) i->set_id(id);}
  148.   /* REQUIRES: Object has been added to locator (has valid id.)
  149.   /* NOTE: Can be NULL. */
  150.  
  151.   void set_health_next(Health h) {healthNext = h;}
  152.   
  153.   virtual void set_mapped_next(Boolean val);
  154.   /* NOTE: Should be ok to set the value to the previous value. */
  155.   /* NOTE: idempotent */
  156.   /* Calls up the tree. */
  157.  
  158.   void set_no_death_delete() {noDeathDelete = True;}
  159.  
  160.   virtual void corporeal_attack(PhysicalP killer,int damage); 
  161.   virtual void heat_attack(PhysicalP,int heat,Boolean secondary = False);
  162.   /* NOTE: Sometimes call up the tree. */
  163.   /* NOTE: killer is the one responsible for causing the damage.  Can be 
  164.      NULL.  Adds kills to the killer. */
  165.   /* NOTE: Only the last call before the update cycle takes effect. */
  166.  
  167.   virtual void avoid(PhysicalP);
  168.   virtual void collide(PhysicalP);
  169.   /* EFFECTS: Collision procedures.  avoid is called on the lighter of the two
  170.      objects.  collide is called on both objects. */
  171.   /* NOTE: Not always called up the tree. */
  172.  
  173.   void intelligence() {if (intel) intel->clock(this);}
  174.  
  175.   void kill_self() {healthNext = -1;}
  176.  
  177.   virtual void set_quiet_death();
  178.   /* EFFECTS: When this dies, do not do any funny things like leaving corpses
  179.      or exploding or any other type of physical evidence. */
  180.   /* NOTE: Calls up the tree. */
  181.  
  182.   void virtual act();
  183.   /* EFFECTS: Action phase.  All next variables must be set here.  Commands 
  184.      are interpreted here.*/
  185.  
  186.   void virtual update(); 
  187.   /* EFFECTS: Set current variables to be the next ones.  No interactions 
  188.      between physical objects. */
  189.   
  190.   void virtual draw(Drawable buffer,Xvars &xvars, const Area &area) = 0;
  191.   /* REQUIRES: buffer is at least as big as area. */
  192.   /* EFFECTS: Draw the physical object in buffer.  buffer represents area. */
  193.   /* NOTE: Does not check for overlap */
  194.   /* NOTE: X variables initialized in draw.  Thus, if draw is never called for
  195.      a base class, the X variables never need to be initialized. */
  196.  
  197.   void virtual die();
  198.   /* EFFECTS:  If the *this dies a natural death (I.e. health < 0), then this
  199.      function is called.  Not called if *this is 
  200.      destroyed for any other reason.  E.g. end of game.  The default is to 
  201.      kill the intel and set_delete_me. */
  202.   /* NOTE: Intel is created/destroyed by Game or Locator. */
  203.   /* NOTE: Should be called in update phase. */
  204.   /* NOTE: Calls up the tree. */
  205.   /* NOTE: Guaranteed to be called only once. */
  206.  
  207.  
  208.   virtual int get_weapons_num();
  209.   virtual int get_items_num(); 
  210.   /* NOTE: Returned value is not valid after current turn. */
  211.   
  212.   virtual PhysicalP get_weapon(int);
  213.   virtual PhysicalP get_item(int); 
  214.   virtual PhysicalP get_weapon_current();
  215.   virtual PhysicalP get_item_current();
  216.   /* NOTE: Can return NULL. */
  217.  
  218.  
  219. #ifndef PROTECTED_IS_PUBLIC
  220. protected:
  221. #endif
  222.   WorldP get_world() {return world;}
  223.  
  224.   Boolean alive_next() {return healthNext >= 0;}
  225.  
  226.   LocatorP get_locator() {return locator;}
  227.  
  228.   const ITcommand &get_command() {return command;}
  229.   /* EFFECTS: Gets the command. */
  230.   /* NOTE: command is not clocked. */
  231.  
  232.   Boolean get_mapped_next() {return mappedNext;}
  233.  
  234.   void set_mass_next(Mass mss) {massNext = mss;}
  235.  
  236.   void set_delete_me() {deleteMe = True;}
  237.  
  238.  
  239. private:
  240.   void init_static();
  241.  
  242.   static Boolean staticValid;
  243.   static Acc unitAccs[CO_DIR_MAX]; 
  244.   static Vel unitVels[CO_DIR_MAX]; 
  245.   Boolean idValid;
  246.   Id id;
  247.   WorldP world;
  248.   LocatorP locator;
  249.   ITcommand command;
  250.   const PhysicalContext *pc; 
  251.   Health health, healthNext;
  252.   Mass mass, massNext;
  253.   PhysicalP dontCollide;
  254.   IntelP intel;
  255.   Boolean deleteMe;
  256.   Boolean mapped,mappedNext;
  257.   Boolean noDeathDelete; // Should set_delete_me be called at death.
  258.   Boolean dieCalled;
  259.   int heat, heatNext;
  260.   Boolean previousHeatWasSecondary;
  261. };
  262. // PhysicalP defined in locator.h
  263.  
  264.  
  265.  
  266. ////////// Moving
  267. // Parent: Physical
  268. // Has all 19 directions.  Multiple pixmaps.  Can change size and position. 
  269. // Top speed is VEL_MAX.
  270.  
  271. /* Only sizes[CO_air] and offsets[CO_air] are required to be set.  
  272.    Gives initial size and offset. */
  273. struct MovingContext {
  274.   char *foreColorName;
  275.   Boolean foreWhiteDefault;
  276.   const char *backColorName;
  277.   Boolean backWhiteDefault;
  278.   int animMax[CO_DIR_MAX];
  279.   Size sizes[CO_DIR_MAX];
  280.   Size offsets[CO_DIR_MAX];
  281.   char *pixmapBits[CO_DIR_MAX][PH_ANIM_MAX];
  282.   char *maskBits[CO_DIR_MAX][PH_ANIM_MAX];
  283.   PhysicalContext physicalContext;
  284. };
  285.  
  286.  
  287. class MovingXdata {
  288. public:
  289.   MovingXdata() {valid = False;}
  290.   
  291.   Boolean valid;
  292.   Pixmap pixmaps[CO_DIR_MAX][PH_ANIM_MAX],
  293.   masks[CO_DIR_MAX][PH_ANIM_MAX];
  294. };
  295.  
  296.  
  297. class Moving: public Physical {
  298. public:
  299.   Moving(const MovingContext &m_c,
  300.      MovingXdata &x_data,
  301.      WorldP world,
  302.      LocatorP l,
  303.      const Pos &rawPos,
  304.      Dir dirInitial = CO_air);
  305.  
  306.   Moving();
  307.   /* NOTE: Should never be called. */
  308.  
  309.   virtual Boolean is_moving();
  310.  
  311.   virtual const Area &get_area();
  312.   virtual Vel get_vel();
  313.   const Pos &get_raw_pos() {return rawPos;}
  314.   virtual Dir get_dir();
  315.  
  316.   void set_middle_next(const Pos &pos);
  317.   /* EFFECTS: Sets the middle of pos according to the current (not next) values
  318.      of dir, and area (for size). */
  319.   /* NOTE: May be called before or after act phase. */
  320.  
  321.   void set_extra_vel_next(const Vel &vel) 
  322.   {extraVelNext = vel; extraVelNextSet = True;}
  323.  
  324.   virtual void act();
  325.   virtual void update();
  326.   virtual void draw(Drawable,Xvars &,const Area &);
  327.   virtual void avoid(PhysicalP);
  328.   virtual void collide(PhysicalP);
  329.  
  330.  
  331. #ifndef PROTECTED_IS_PUBLIC
  332. protected:
  333. #endif
  334.   Boolean hit_wall() {return hitWall;}
  335.   Boolean hit_wall_next() {return hitWallNext;}
  336.  
  337.   Dir get_dir_next() {return dirNext;}
  338.  
  339.   const Area &get_area_next() {return areaNext;}
  340.   const MovingContext *get_moving_context() {return mc;}
  341.   Vel get_vel_next() {return velNext;}
  342.  
  343.   void set_vel(const Vel &v) {vel = v;}
  344.  
  345.   void set_vel_next(const Vel &vel) {velNext = vel;}
  346.   void set_vel_next(int zero) {assert (zero == 0); velNext.set_zero();}
  347.   /* EFFECTS: Sets the next velocity for the object to be vel.  Can be called
  348.      multiple times before update, only the last call is used. */
  349.  
  350. //  void set_extra_vel(const Vel &vel) {extraVel = vel;}
  351.   /* NOTE: Not clocked. */
  352.   
  353.   void set_dir(const Dir &d) {dir = d;}
  354.   /* NOTE: Only used by Lance for initialization. */
  355.  
  356.   void set_dir_next(const Dir &d) {dirNext = d;}
  357.  
  358.   void set_raw_pos_next(const Pos &rpos)
  359.     {rawPosNext = rpos; rawPosChanged = True;}
  360.  
  361.   void update_next();
  362.   /* EFFECTS: Compute areaNext and hitWallNext.  May modify rawPosNext or 
  363.      dirNext. */
  364.   /* NOTE: May be called more than once per turn. */
  365.  
  366.   virtual void get_pixmap_mask(Pixmap &pixmap,Pixmap &mask,
  367.                    Dir dir,int animNum);
  368.   /* MODIFIES: pixmap, mask */
  369.   /* NOTE: Only used so that children of Moving can affect Moving's actions. */
  370.   
  371.   virtual void get_size_offset_next(Size &size,Size &offset,Dir dirNext);
  372.   /* MODIFIES: size, offset */
  373.   /* NOTE: Only used so that children of Moving can affect Moving's actions. */
  374.  
  375.   virtual void init_x(Xvars &);
  376.   /* NOTE: Now called up the tree. */
  377.  
  378.  
  379. private:
  380.   Boolean context_valid();
  381.   /* EFFECTS: Returns True if this->cx is valid, False otherwise. */
  382.  
  383.   float compute_collision(Mass m1,float v1,Mass m2,float v2);
  384.  
  385.  
  386.   MovingXdata *movingXdata;
  387.   int movingAnimNum;
  388.   Timer animTimer;
  389.   const MovingContext *mc;
  390.   Pos rawPos,rawPosNext; Boolean rawPosChanged;
  391.   Area area,areaNext;   
  392.   Dir dir,dirNext;
  393.   Vel vel,velNext; 
  394.   Boolean extraVelNextSet;
  395.   Vel extraVel,extraVelNext; // Follows clock in non-standard way.
  396.   Boolean hitWall,hitWallNext;
  397. };
  398. typedef Moving *MovingP;
  399.  
  400.  
  401.  
  402. ////////// Shot
  403. // Parent: Moving
  404.  
  405. struct ShotContext {
  406.   int damage;  // Or heat.
  407.   Speed speed;
  408.   MovingContext movingContext;
  409. };
  410.  
  411. typedef MovingXdata ShotXdata ;
  412.  
  413. class Shot: public Moving {
  414. public:
  415.   Shot(const ShotContext &,ShotXdata &,WorldP,LocatorP,
  416.        const Pos &,const Id &shooter,
  417.        Dir shotDir,Dir movingDir = CO_air);
  418.   
  419.   const Id &get_shooter() {return shooter;}
  420.  
  421.   virtual Boolean is_shot();
  422.  
  423.   virtual void avoid(PhysicalP other);
  424.   virtual void collide(PhysicalP other);
  425.  
  426.   virtual void update();
  427.  
  428.  
  429. #ifndef PROTECTED_IS_PUBLIC
  430.  protected:
  431. #endif
  432.   int get_damage() {return context->damage;}
  433.  
  434.  
  435. private:
  436.   Id shooter;
  437.   const ShotContext *context;
  438. };
  439.  
  440.  
  441.  
  442. ////////// Falling
  443. // Parent: Moving
  444. // Moving with gravity.  Falls until it is blocked by the world.  
  445.  
  446. struct FallingContext {
  447.   MovingContext movingContext;
  448. };
  449.  
  450. typedef MovingXdata FallingXdata;
  451.  
  452. class Falling: public Moving {
  453. public:
  454.   Falling(const FallingContext &h_c,FallingXdata &x_data,
  455.       WorldP world,LocatorP l,const Pos &rawPos,
  456.       Dir dirInitial = CO_air);
  457.   
  458.   virtual void act();
  459. };
  460.  
  461.  
  462.  
  463. //////////// Heavy
  464. // Parent: Falling
  465. // Does damage to things it lands on.
  466.  
  467. struct HeavyContext {
  468.   int damage;
  469.   FallingContext fallingContext;
  470. };
  471.  
  472. typedef FallingXdata HeavyXdata;
  473.  
  474. class Heavy: public Falling {
  475.  public:
  476.   Heavy(const HeavyContext &h_c,
  477.     HeavyXdata &x_data,
  478.     WorldP world,
  479.     LocatorP l,
  480.     const Pos &rawPos);
  481.   
  482.   virtual void collide(PhysicalP);
  483.   /* EFFECTS: Crush things it falls on. */
  484.   
  485.  
  486.  private:
  487.   const HeavyContext *context;
  488. };
  489.  
  490.  
  491.  
  492. //////////// Generator
  493. // Parent: Heavy
  494. // Generate machines and register them with the locator.
  495.  
  496. struct GeneratorContext {
  497.   HeavyContext heavyContext;
  498. };
  499.  
  500. typedef HeavyXdata GeneratorXdata;
  501.  
  502. class Generator: public Heavy {
  503. public:
  504.   Generator(const IntelOptions &ops,ITmask opMask,
  505.         const char *prefix,
  506.         const GeneratorContext &g_c,
  507.         GeneratorXdata &x_data,
  508.         WorldP w,
  509.         LocatorP l,
  510.         const Pos &rawPos);
  511.   
  512.   virtual void act();
  513.   
  514.   
  515. #ifndef PROTECTED_IS_PUBLIC
  516. protected:
  517. #endif
  518.   virtual PhysicalP generate() = 0;
  519.   
  520.   
  521. private:
  522.   enum {MAX = 10, TIME = 100};
  523.  
  524.   Timer timer;
  525.   int machineCount; // Always increasing.
  526.   IntelOptions machineOps;
  527.   ITmask machineOpMask;
  528.   const char *machinePrefix;
  529.  
  530.   Id generated[MAX];
  531.   const GeneratorContext *generatorContext;
  532. };
  533.  
  534.  
  535.  
  536. //////////// Item
  537. // Parent: Falling
  538. // 
  539. struct ItemContext {
  540.   Boolean persists;
  541.   FallingContext fallingContext;
  542. };
  543. typedef FallingXdata ItemXdata;
  544.  
  545.  
  546. class Item: public Falling {
  547. public:
  548.   Item(const ItemContext &c_x,
  549.        ItemXdata &x_data,
  550.        WorldP w,
  551.        LocatorP l,
  552.        const Pos &pos);
  553.   
  554.   Boolean is_item() {return True;}
  555.  
  556.   Boolean is_held() {return held;}
  557.   
  558.   Boolean can_take() {return canTake.ready() && !held && !cantTake;}
  559.   /* EFFECTS: Returns whether the object can be picked up. */
  560.  
  561.   virtual int get_drawing_level();
  562.   /* NOTE: Items are at drawing level 1. */
  563.  
  564.   Boolean persists() {return context->persists;}
  565.  
  566.   virtual void follow_user(const Pos &userMiddle,Dir userDir);
  567.  
  568.   void taken(PhysicalP);
  569.   /* EFFECTS:  The object has been taken by another Physical. */
  570.   /* NOTE: Changes immediate externally visible state.  Should only be called
  571.      in the collision phase. */
  572.  
  573.   void dropped(PhysicalP);
  574.   /* EFFECTS:  The object has been dropped by another Physical. */
  575.   /* NOTE: Called by another object in the act phase. */
  576.   /* NOTE: Called in either the act or update phase. */
  577.   /* NOTE: Calls up the tree. */
  578.  
  579.   virtual void use(PhysicalP);
  580.   /* EFFECTS: p uses *this. */
  581.   /* NOTE: Called by another object in act phase. */
  582.  
  583.   void set_used_message() {usedMessage = True;}
  584.   /* EFFECTS: On death, the printed message will say the item was used instead
  585.      of saying the item was destroyed. */
  586.   
  587.   virtual void act();
  588.   
  589.   virtual void die();
  590.   
  591.   
  592. #ifndef PROTECTED_IS_PUBLIC
  593. protected:
  594. #endif
  595.   void set_cant_take() {cantTake = True;}
  596.   
  597.   
  598. private:
  599.   Boolean held;
  600.   Boolean usedMessage;
  601.   Timer canTake;
  602.   Boolean cantTake;
  603.   const ItemContext *context;
  604. };
  605. typedef Item *ItemP;
  606.  
  607.  
  608.  
  609. //////////// Animated
  610. // Parent: Item
  611. //
  612. struct AnimatedContext {
  613.   char *colorName;
  614.   Size size;
  615.   int animMax[PH_FRAME_MAX];
  616.   char *pixmapBits[PH_FRAME_MAX][PH_ANIM_MAX];
  617.   char *maskBits[PH_FRAME_MAX][PH_ANIM_MAX];
  618.   ItemContext itemContext;
  619. };
  620.  
  621.  
  622. class AnimatedXdata {
  623. public:
  624.   AnimatedXdata() {valid = False;}
  625.   Boolean valid;
  626.   Pixmap pixmaps[PH_FRAME_MAX][PH_ANIM_MAX],
  627.   masks[PH_FRAME_MAX][PH_ANIM_MAX];
  628.   ItemXdata itemXdata;
  629. }; 
  630.  
  631.  
  632. class Animated: public Item {
  633. public:
  634.   Animated::Animated(const AnimatedContext &,AnimatedXdata &,
  635.              WorldP,LocatorP,const Pos &);
  636.  
  637.  
  638. #ifndef PROTECTED_IS_PUBLIC
  639. protected:
  640. #endif
  641.   void set_frame(Frame fr) {frame = fr;}
  642.   void set_frame_next(Frame fr) {frameNext = fr;}
  643.   Frame get_frame() {return frame;}
  644.   
  645.   virtual void get_pixmap_mask(Pixmap &pixmap,Pixmap &mask,
  646.                    Dir dir,int animNum);
  647.   virtual void get_size_offset_next(Size &size,Size &offset,
  648.                     Dir dirNext);
  649.   
  650.   virtual void init_x(Xvars &);
  651.   
  652.   virtual void update();
  653.  
  654.  
  655. private:
  656.   Boolean context_valid();
  657.  
  658.   AnimatedXdata *animatedXdata;
  659.   const AnimatedContext *ac;
  660.   Frame frame,frameNext;
  661.   int animatedAnimNum;
  662. };
  663.  
  664.  
  665.  
  666. //////////// Weapon
  667. // Parent: Item
  668. // 
  669. struct WeaponContext {
  670.   Boolean defaultable;
  671.   ItemContext itemContext;
  672. };
  673. typedef ItemXdata WeaponXdata;
  674. class Weapon;
  675. typedef Weapon *WeaponP;
  676.  
  677.  
  678. class Weapon: public Item {
  679. public:
  680.   Weapon(const WeaponContext &c_x,
  681.      WeaponXdata &x_data,
  682.      WorldP w,
  683.      LocatorP l,
  684.      const Pos &pos);
  685.   
  686.   Boolean is_weapon() {return True;}
  687.  
  688.   virtual Boolean ready() = 0;
  689.   /* EFFECTS: Can the weapon be fired now. */
  690.   /* NOTE: Sometimes calls up the tree.*/
  691.  
  692.   Boolean defaultable() {return wc->defaultable;}
  693.   /* EFFECTS: Is this a type of weapon that can safely be set automatically as
  694.      the current weapon.  E.g. You do not want to set a soul-swapper as the 
  695.      current weapon unless the user explicitly says so. */
  696.  
  697.   virtual int get_ammo() = 0;
  698.   virtual int get_ammo_max() = 0;
  699.   /* NOTE: Can return PH_AMMO_UNLIMITED. */
  700.  
  701.   virtual void fire(const Id &id,ITcommand command);
  702.   /* REQUIRES: command is a weapon command. */
  703.   /* EFFECTS: Fire the weapon according to the specified command.  id is the
  704.      physical firing the weapon.  */
  705.  
  706.   virtual void enter_scope_next(PhysicalP user);
  707.   virtual void leave_scope_next(PhysicalP user);
  708.   /* NOTE: Called during act(collide) or update phase. Should be just 
  709.      act(). */
  710.   /* NOTE: Calls up the tree. */
  711.   /* NOTE: ok to call multiple times in same turn, but must enter/leave scope
  712.      in proper order. */
  713.  
  714.   void take_ammo_from(WeaponP other);
  715.   /* EFFECTS: Take as much ammo as possible from the other weapon. */
  716.  
  717.  
  718. #ifndef PROTECTED_IS_PUBLIC
  719.  protected:
  720. #endif
  721.   Boolean entered_scope() {return enteredScope;}
  722.  
  723.   virtual void set_ammo(int) = 0;
  724.  
  725.  
  726. private:
  727.   const WeaponContext *wc;
  728.   Boolean enteredScope; // not clocked
  729. };
  730. // typedef Weapon *WeaponP; Defined above.
  731.  
  732.  
  733.  
  734. //////////// Cutter
  735. // Parent: Weapon
  736. // NOTE: Uses CO_center for cutter directly in front of user.
  737. struct CutterContext {
  738.   int damage;  // per turn
  739.   Size offsets[CO_DIR_MAX];  // From User's middle to Cutter's middle.
  740.  
  741.   char *unheldColorName;
  742.   Size unheldSize;
  743.   char *unheldPixmapBits;
  744.   char *unheldMaskBits;
  745.   WeaponContext weaponContext;
  746. };
  747.  
  748.  
  749. class CutterXdata {
  750.  public:
  751.   CutterXdata() {valid = False;}
  752.  
  753.   Boolean valid;
  754.   Pixmap unheldPixmap,unheldMask;
  755.   WeaponXdata weaponXdata;
  756. };
  757.  
  758.  
  759. class Cutter: public Weapon {
  760. public:
  761.   Cutter(const CutterContext &c_x,CutterXdata &x_data,
  762.      WorldP w,LocatorP l,const Pos &pos);
  763.   
  764.   virtual Boolean is_cutter();
  765.  
  766.   virtual Boolean ready();
  767.  
  768.   virtual int get_ammo();
  769.   virtual int get_ammo_max();
  770.  
  771.   virtual void get_pixmap_mask(Pixmap &pixmap,Pixmap &mask,
  772.                    Dir dir,int animNum);
  773.   
  774.   virtual void get_size_offset_next(Size &size,Size &offset,Dir dirNext);
  775.  
  776.   virtual void set_ammo(int);
  777.  
  778.   virtual void follow_user(const Pos &,Dir);
  779.  
  780.   virtual void enter_scope_next(PhysicalP);
  781.   virtual void leave_scope_next(PhysicalP);
  782.  
  783.   virtual void collide(PhysicalP);
  784.  
  785.   virtual void update();
  786.  
  787.  
  788. #ifndef PROTECTED_IS_PUBLIC
  789.  protected: 
  790. #endif
  791.   virtual void init_x(Xvars &);
  792.  
  793.  
  794. private:
  795.   Dir dir_4_from_user_dir(Dir);
  796.  
  797.   Boolean inScope,inScopeNext;
  798.   Id killerId;  // Valid iff inScope.
  799.   CutterXdata *cutterXdata;
  800.   const CutterContext *context;
  801. };
  802. #endif
  803.  
  804.